home *** CD-ROM | disk | FTP | other *** search
/ Sprite 1984 - 1993 / Sprite 1984 - 1993.iso / src / daemons / lpd / RCS / rmjob.c,v < prev   
Encoding:
Text File  |  1992-04-19  |  6.9 KB  |  322 lines

  1. head     1.1;
  2. branch   ;
  3. access   ;
  4. symbols  ;
  5. locks    ; strict;
  6. comment  @ * @;
  7.  
  8.  
  9. 1.1
  10. date     88.11.23.10.34.11;  author rab;  state Exp;
  11. branches ;
  12. next     ;
  13.  
  14.  
  15. desc
  16. @@
  17.  
  18.  
  19.  
  20. 1.1
  21. log
  22. @Initial revision
  23. @
  24. text
  25. @/*
  26.  * Copyright (c) 1983 Regents of the University of California.
  27.  * All rights reserved.
  28.  *
  29.  * Redistribution and use in source and binary forms are permitted
  30.  * provided that this notice is preserved and that due credit is given
  31.  * to the University of California at Berkeley. The name of the University
  32.  * may not be used to endorse or promote products derived from this
  33.  * software without specific prior written permission. This software
  34.  * is provided ``as is'' without express or implied warranty.
  35.  */
  36.  
  37. #ifndef lint
  38. static char sccsid[] = "@@(#)rmjob.c    5.2 (Berkeley) 5/5/88";
  39. #endif /* not lint */
  40.  
  41. /*
  42.  * rmjob - remove the specified jobs from the queue.
  43.  */
  44.  
  45. #include "lp.h"
  46.  
  47. /*
  48.  * Stuff for handling lprm specifications
  49.  */
  50. extern char    *user[];        /* users to process */
  51. extern int    users;            /* # of users in user array */
  52. extern int    requ[];            /* job number of spool entries */
  53. extern int    requests;        /* # of spool requests */
  54. extern char    *person;        /* name of person doing lprm */
  55.  
  56. char    root[] = "root";
  57. int    all = 0;        /* eliminate all files (root only) */
  58. int    cur_daemon;        /* daemon's pid */
  59. char    current[40];        /* active control file name */
  60.  
  61. int    iscf();
  62.  
  63. rmjob()
  64. {
  65.     register int i, nitems;
  66.     int assasinated = 0;
  67.     struct direct **files;
  68.  
  69.     if ((i = pgetent(line, printer)) < 0)
  70.         fatal("cannot open printer description file");
  71.     else if (i == 0)
  72.         fatal("unknown printer");
  73.     if ((SD = pgetstr("sd", &bp)) == NULL)
  74.         SD = DEFSPOOL;
  75.     if ((LO = pgetstr("lo", &bp)) == NULL)
  76.         LO = DEFLOCK;
  77.     if ((LP = pgetstr("lp", &bp)) == NULL)
  78.         LP = DEFDEVLP;
  79.     if ((RP = pgetstr("rp", &bp)) == NULL)
  80.         RP = DEFLP;
  81.     RM = pgetstr("rm", &bp);
  82.  
  83.     /*
  84.      * If the format was `lprm -' and the user isn't the super-user,
  85.      *  then fake things to look like he said `lprm user'.
  86.      */
  87.     if (users < 0) {
  88.         if (getuid() == 0)
  89.             all = 1;    /* all files in local queue */
  90.         else {
  91.             user[0] = person;
  92.             users = 1;
  93.         }
  94.     }
  95.     if (!strcmp(person, "-all")) {
  96.         if (from == host)
  97.             fatal("The login name \"-all\" is reserved");
  98.         all = 1;    /* all those from 'from' */
  99.         person = root;
  100.     }
  101.  
  102.     if (chdir(SD) < 0)
  103.         fatal("cannot chdir to spool directory");
  104.     if ((nitems = scandir(".", &files, iscf, NULL)) < 0)
  105.         fatal("cannot access spool directory");
  106.  
  107.     if (nitems) {
  108.         /*
  109.          * Check for an active printer daemon (in which case we
  110.          *  kill it if it is reading our file) then remove stuff
  111.          *  (after which we have to restart the daemon).
  112.          */
  113.         if (lockchk(LO) && chk(current)) {
  114.             assasinated = kill(cur_daemon, SIGINT) == 0;
  115.             if (!assasinated)
  116.                 fatal("cannot kill printer daemon");
  117.         }
  118.         /*
  119.          * process the files
  120.          */
  121.         for (i = 0; i < nitems; i++)
  122.             process(files[i]->d_name);
  123.     }
  124.     chkremote();
  125.     /*
  126.      * Restart the printer daemon if it was killed
  127.      */
  128.     if (assasinated && !startdaemon(printer))
  129.         fatal("cannot restart printer daemon\n");
  130.     exit(0);
  131. }
  132.  
  133. /*
  134.  * Process a lock file: collect the pid of the active
  135.  *  daemon and the file name of the active spool entry.
  136.  * Return boolean indicating existence of a lock file.
  137.  */
  138. lockchk(s)
  139.     char *s;
  140. {
  141.     register FILE *fp;
  142.     register int i, n;
  143.  
  144.     if ((fp = fopen(s, "r")) == NULL)
  145.         if (errno == EACCES)
  146.             fatal("can't access lock file");
  147.         else
  148.             return(0);
  149.     if (!getline(fp)) {
  150.         (void) fclose(fp);
  151.         return(0);        /* no daemon present */
  152.     }
  153.     cur_daemon = atoi(line);
  154.     if (kill(cur_daemon, 0) < 0) {
  155.         (void) fclose(fp);
  156.         return(0);        /* no daemon present */
  157.     }
  158.     for (i = 1; (n = fread(current, sizeof(char), sizeof(current), fp)) <= 0; i++) {
  159.         if (i > 5) {
  160.             n = 1;
  161.             break;
  162.         }
  163.         sleep(i);
  164.     }
  165.     current[n-1] = '\0';
  166.     (void) fclose(fp);
  167.     return(1);
  168. }
  169.  
  170. /*
  171.  * Process a control file.
  172.  */
  173. process(file)
  174.     char *file;
  175. {
  176.     FILE *cfp;
  177.  
  178.     if (!chk(file))
  179.         return;
  180.     if ((cfp = fopen(file, "r")) == NULL)
  181.         fatal("cannot open %s", file);
  182.     while (getline(cfp)) {
  183.         switch (line[0]) {
  184.         case 'U':  /* unlink associated files */
  185.             if (from != host)
  186.                 printf("%s: ", host);
  187.             printf(unlink(line+1) ? "cannot dequeue %s\n" :
  188.                 "%s dequeued\n", line+1);
  189.         }
  190.     }
  191.     (void) fclose(cfp);
  192.     if (from != host)
  193.         printf("%s: ", host);
  194.     printf(unlink(file) ? "cannot dequeue %s\n" : "%s dequeued\n", file);
  195. }
  196.  
  197. /*
  198.  * Do the dirty work in checking
  199.  */
  200. chk(file)
  201.     char *file;
  202. {
  203.     register int *r, n;
  204.     register char **u, *cp;
  205.     FILE *cfp;
  206.  
  207.     /*
  208.      * Check for valid cf file name (mostly checking current).
  209.      */
  210.     if (strlen(file) < 7 || file[0] != 'c' || file[1] != 'f')
  211.         return(0);
  212.  
  213.     if (all && (from == host || !strcmp(from, file+6)))
  214.         return(1);
  215.  
  216.     /*
  217.      * get the owner's name from the control file.
  218.      */
  219.     if ((cfp = fopen(file, "r")) == NULL)
  220.         return(0);
  221.     while (getline(cfp)) {
  222.         if (line[0] == 'P')
  223.             break;
  224.     }
  225.     (void) fclose(cfp);
  226.     if (line[0] != 'P')
  227.         return(0);
  228.  
  229.     if (users == 0 && requests == 0)
  230.         return(!strcmp(file, current) && isowner(line+1, file));
  231.     /*
  232.      * Check the request list
  233.      */
  234.     for (n = 0, cp = file+3; isdigit(*cp); )
  235.         n = n * 10 + (*cp++ - '0');
  236.     for (r = requ; r < &requ[requests]; r++)
  237.         if (*r == n && isowner(line+1, file))
  238.             return(1);
  239.     /*
  240.      * Check to see if it's in the user list
  241.      */
  242.     for (u = user; u < &user[users]; u++)
  243.         if (!strcmp(*u, line+1) && isowner(line+1, file))
  244.             return(1);
  245.     return(0);
  246. }
  247.  
  248. /*
  249.  * If root is removing a file on the local machine, allow it.
  250.  * If root is removing a file from a remote machine, only allow
  251.  * files sent from the remote machine to be removed.
  252.  * Normal users can only remove the file from where it was sent.
  253.  */
  254. isowner(owner, file)
  255.     char *owner, *file;
  256. {
  257.     if (!strcmp(person, root) && (from == host || !strcmp(from, file+6)))
  258.         return(1);
  259.     if (!strcmp(person, owner) && !strcmp(from, file+6))
  260.         return(1);
  261.     if (from != host)
  262.         printf("%s: ", host);
  263.     printf("%s: Permission denied\n", file);
  264.     return(0);
  265. }
  266.  
  267. /*
  268.  * Check to see if we are sending files to a remote machine. If we are,
  269.  * then try removing files on the remote machine.
  270.  */
  271. chkremote()
  272. {
  273.     register char *cp;
  274.     register int i, rem;
  275.     char buf[BUFSIZ];
  276.  
  277.     if (*LP || RM == NULL)
  278.         return;    /* not sending to a remote machine */
  279.  
  280.     /*
  281.      * Flush stdout so the user can see what has been deleted
  282.      * while we wait (possibly) for the connection.
  283.      */
  284.     fflush(stdout);
  285.  
  286.     sprintf(buf, "\5%s %s", RP, all ? "-all" : person);
  287.     cp = buf;
  288.     for (i = 0; i < users; i++) {
  289.         cp += strlen(cp);
  290.         *cp++ = ' ';
  291.         strcpy(cp, user[i]);
  292.     }
  293.     for (i = 0; i < requests; i++) {
  294.         cp += strlen(cp);
  295.         (void) sprintf(cp, " %d", requ[i]);
  296.     }
  297.     strcat(cp, "\n");
  298.     rem = getport(RM);
  299.     if (rem < 0) {
  300.         if (from != host)
  301.             printf("%s: ", host);
  302.         printf("connection to %s is down\n", RM);
  303.     } else {
  304.         i = strlen(buf);
  305.         if (write(rem, buf, i) != i)
  306.             fatal("Lost connection");
  307.         while ((i = read(rem, buf, sizeof(buf))) > 0)
  308.             (void) fwrite(buf, 1, i, stdout);
  309.         (void) close(rem);
  310.     }
  311. }
  312.  
  313. /*
  314.  * Return 1 if the filename begins with 'cf'
  315.  */
  316. iscf(d)
  317.     struct direct *d;
  318. {
  319.     return(d->d_name[0] == 'c' && d->d_name[1] == 'f');
  320. }
  321. @
  322.